﻿using System;

using SharpOSCAR.Base;

namespace SharpOSCAR.Flap
{
    /// <summary>
    /// These tags are used in the FLAP signon frame. They appear right after the 4 byte version number.
    /// </summary>
    public class FLAP__SIGNON_FRAME : FLAP__HEADER
    {
        private const ushort FLAP_SIGNON_CLIENTNAME = 3;
        private const ushort FLAP_SIGNON_LOGINCOOKIE = 6;
        private const ushort FLAP_SIGNON_MAJORVERSION = 23;
        private const ushort FLAP_SIGNON_MINORVERSION = 24;
        private const ushort FLAP_SIGNON_REVISION = 25;
        private const ushort FLAP_SIGNON_BUILDNUMBER = 26;
        private const ushort FLAP_SIGNON_MULTICONN_FLAGS = 74;

        private TlvArray _TLVs;

        /// <summary>
        /// Initializes the FLAP signon packet with the specified SeqNum and login cookie
        /// </summary>
        /// <param name="sequenceNumber">Sequential number; initialize to random value</param>
        /// <param name="loginCookie">Login cookie returned by startOSCARSession</param>
        public FLAP__SIGNON_FRAME(ushort sequenceNumber, byte[] loginCookie)
            : this(sequenceNumber, loginCookie, "abc")
        { }

        /// <summary>
        /// Initializes the FLAP signon packet with the specified SeqNum, login cookie, and client name
        /// </summary>
        /// <param name="sequenceNumber">Sequential number; initialize to random value</param>
        /// <param name="loginCookie">Login cookie returned by startOSCARSession</param>
        /// <param name="clientName">Name of the client</param>
        public FLAP__SIGNON_FRAME(ushort sequenceNumber, byte[] loginCookie, string clientName)
            : this(sequenceNumber, loginCookie, clientName, null)
        { }
        
        /// <summary>
        /// Initializes the FLAP signon packet with the specified SeqNum, login cookie, client name, and version
        /// </summary>
        /// <param name="sequenceNumber">Sequential number; initialize to random value</param>
        /// <param name="loginCookie">Login cookie returned by startOSCARSession</param>
        /// <param name="clientName">Name of the client</param>
        /// <param name="clientVersion">Version of the client</param>
        public FLAP__SIGNON_FRAME(ushort sequenceNumber, byte[] loginCookie, string clientName, Version clientVersion)
            : base(sequenceNumber)
        {
            DataArray da = new DataArray();
            da.Add(new U32(1));
            _TLVs = new TlvArray();
            _TLVs.AddTlv(new Tlv(FLAP_SIGNON_CLIENTNAME, new SharpOSCAR.Base.String(clientName)));
            _TLVs.AddTlv(new Tlv(FLAP_SIGNON_LOGINCOOKIE, new Blob(loginCookie)));

            if (clientVersion == null)
                clientVersion = new Version(0, 1, 0, 0);

            _TLVs.AddTlv(new Tlv(FLAP_SIGNON_MAJORVERSION, new U16((ushort)clientVersion.Major)));
            _TLVs.AddTlv(new Tlv(FLAP_SIGNON_MINORVERSION, new U16((ushort)clientVersion.Minor)));
            _TLVs.AddTlv(new Tlv(FLAP_SIGNON_REVISION, new U16((ushort)clientVersion.Revision)));
            _TLVs.AddTlv(new Tlv(FLAP_SIGNON_BUILDNUMBER, new U16((ushort)clientVersion.Build)));

            _TLVs.AddTlv(new Tlv(FLAP_SIGNON_MULTICONN_FLAGS, new U8((byte)FLAP__MULTICONN_FLAGS.Supported)));
            da.Add(_TLVs);
            // Assign the payload for the packet
            Payload = da;
        }

        /// <summary>
        /// Return the FLAP frame type of the packet
        /// </summary>
        public override FLAP__FRAME_TYPE FrameType
        {
            get { return FLAP__FRAME_TYPE.Signon; }
        }
    }
}
